//
//  main.m
//  Memory2
//
//  Created by cora1n on 14-8-11.
//  Copyright (c) 2014年 devwu. All rights reserved.
//

#import <Foundation/Foundation.h>
#import "Person.h"
#import "Car.h"
int main(int argc, const char * argv[])
{
    //该对象被引用几次,它的引用技术就是几
    //内存中常见问题:
    //该管的不管:
    //内存开辟了,却不去释放   ---> 内存泄露
    //不该管的管的也管:
    //不是自己开辟的,偏要去释放---> 过度释放,运行时错误
    
    Car * c1 = [[Car alloc]init];
    c1.brand = @"大奔";
    NSLog(@"c1 的引用计数为: %lu",c1.retainCount);
    Person * p1 = [[Person alloc]init];
//    [p1 setCar:c1];
//    NSLog(@"c1 的引用技术为 : %lu",c1.retainCount);
//    [c1 release];
    //p1.car 指向的那块地址已经被释放,不可访问
//    [p1.car release];
    
    Car * c2 = [p1 someCar];
    NSLog(@"c2 的引用计数为: %lu",c2.retainCount);
//    //为了避免因c2 改变指向而发生的内存泄露,在改变指向前,先release一下
//    
//    
//    //自动释放池
//    NSLog(@"创建池");
////    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc]init];
//    @autoreleasepool {
//        Car * c3 = [[Car alloc]init];
//        c3.brand = @"test";
//        [c3 autorelease];
//    }
//    //在alloc pool 到 drain pool之间的代码,均属于该pool管理
//    
////    Car * c3 = [[Car alloc]init];
////    c3.brand = @"test";
////    [c3 autorelease];
//    
//    
////    [pool drain];
//    //在清空池时,会将池内书写的所有的调用了autorelease的对象release方法
//    NSLog(@"清空池");
//    
//    c2 = [p1 someCar];
//    NSLog(@"c2 的引用计数为: %lu",c2.retainCount);
    
    
    
    
    
    //延迟释放的应用
    //初始化方法   [[A alloc]initWith:(XXX*)xxx];
    //工厂方法    [A aWith:(XXX*)xxx];
    
    //延迟释放的缺陷
    //1.造成内存峰值过高
    //2.延迟释放时间不确定
    
    //尽量避免autorelease
    //如果必须使用autorelease时,则将它加入到自动释放池
    
    //当应用内存高居不下时,应从自动释放池的角度去考虑问题
//    for (int i = 0; i<100000; i++) {
//        @autoreleasepool {
//            [Person personWithName:@"test"];
//        }
//        Person * p1 = [[Person alloc]initWithName:@"test"];
//        [p1 release];
        
//    }
    
    
    
    return 0;
}

